iT邦幫忙

第 12 屆 iThome 鐵人賽

DAY 14
0

今天還是沿著繼續講 directive,不過與之前介紹的 attribute directive 不同,今天要介紹的是 structural directive,而且也不算是 Tip,而是比較像是要來分享 * 語法糖與 microsyntax 的小知識!

你應該要知道的事

其實這個 section 應該就是主文了 ?

官方文件有提到,這個「*」(星號,Asterisk)其實是一種甜的要命的語法糖,當我們按照下列範例來寫的時候:

// HTML
<p *ngFor="let item of tempList">{{item}}</p>

// TypeScript
@Component({
  selector: 'app-root',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.scss']
})
export class AppComponent {
  title = 'day14';
  tempList = [
    'a',
    'b',
    'c',
    'd'
  ];
}

↑ Block 1:*ngFor 範例

function AppComponent_p_0_Template(rf, ctx) { if (rf & 1) {
    _angular_core__WEBPACK_IMPORTED_MODULE_0__["ɵɵelementStart"](0, "p");
    _angular_core__WEBPACK_IMPORTED_MODULE_0__["ɵɵtext"](1);
    _angular_core__WEBPACK_IMPORTED_MODULE_0__["ɵɵelementEnd"]();
} if (rf & 2) {
    const item_r1 = ctx.$implicit;
    _angular_core__WEBPACK_IMPORTED_MODULE_0__["ɵɵadvance"](1);
    _angular_core__WEBPACK_IMPORTED_MODULE_0__["ɵɵtextInterpolate"](item_r1);
} }

↑ Block 2:Block 1 經過 compile 的結果

現在我們來看一下透過 ng-template 來寫的程式碼:

// HTML
<ng-template ngFor let-item [ngForOf]="tempList">
  <p>{{item}}</p>
</ng-template>

↑ Block 3:ng-template 範例

function AComponent_ng_template_0_Template(rf, ctx) { if (rf & 1) {
    _angular_core__WEBPACK_IMPORTED_MODULE_0__["ɵɵelementStart"](0, "p");
    _angular_core__WEBPACK_IMPORTED_MODULE_0__["ɵɵtext"](1);
    _angular_core__WEBPACK_IMPORTED_MODULE_0__["ɵɵelementEnd"]();
} if (rf & 2) {
    const item_r1 = ctx.$implicit;
    _angular_core__WEBPACK_IMPORTED_MODULE_0__["ɵɵadvance"](1);
    _angular_core__WEBPACK_IMPORTED_MODULE_0__["ɵɵtextInterpolate"](item_r1);
} }

↑ Block 4:ng-template 經過 compile 的結果

以編譯後的結果來說,對於 Angular 來說,你用 * 或是 ng-template 兩者是一樣的!


我們回頭看一下 Block 1,程式碼內用到的 let item of tempList 這種寫法,Angular 將之稱為:microsyntax。microsyntax 有一些簡單的規範(畢竟是 micro 而已),舉例來說,let item 的部分會被視為 template input variable、of tempList 的部分則會被視為 [ngForOf]="tempList"。完整的對應機制如下(引用自官方來源):

https://ithelp.ithome.com.tw/upload/images/20200929/2012914889pZ2PXHRf.png

↑ Image 2

所以當我們像下圖這樣不小心寫錯的時候,它的錯誤訊息就會跟你說:"Property binding ngForIn not used by any directive on an embedded template.",因為 Angular 壓根就不認識這個東西,但如果你自己寫了另外一個 structural directive 就另當別論了……

https://ithelp.ithome.com.tw/upload/images/20200929/20129148jB3oO9BSrt.png

↑ Image 2


以上就是今天要分享的小知識!

原本其實還打算要找出 Angular 是先將 * 語法糖轉成 ng-template 還是直接 compile 的,但因為時間壓力只好先暫緩這部分的研究了 ?

日後有機會的話會再補上!

準備過中秋 ?

以下按照入團順序列出我們團隊夥伴的系列文章!


上一篇
[Day 13] exportAs,透過 template variable 取得 directive 實體
下一篇
[Day 15] 微探討 FormControl 跟 HTML input element 的 value 怎麼互動
系列文
從巨人的 Tip 看 Angular30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言